package com.gyh.shiro;

import java.util.Map;

import javax.servlet.DispatcherType;
import javax.servlet.Filter;

import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.filter.authc.AnonymousFilter;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.apache.shiro.web.session.mgt.ServletContainerSessionManager;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.filter.DelegatingFilterProxy;

import com.google.common.collect.Maps;

@Configuration
public class ShiroConfig {

	private static final Logger logger = LoggerFactory.getLogger(ShiroConfig.class);
	
	//配置注册shiro的bean
	public FilterRegistrationBean filterRegisterationBean() {
		logger.info("执行了finterRegisterationBean方法。。。。");
		FilterRegistrationBean filterRegistration = new FilterRegistrationBean();
		filterRegistration.setFilter(new DelegatingFilterProxy("shiroFilter"));
		filterRegistration.setEnabled(true); //标记表明注册已启用。
		filterRegistration.addUrlPatterns("/*"); //添加过滤器将被注册的URL模式。
		filterRegistration.setDispatcherTypes(DispatcherType.REQUEST);//设置应该用于注册的调度程序类型。如果不是指定类型将根据其值进行推断
		return filterRegistration;
	}
	
	
	
	//配置shiro的拦截器
	
	@Bean(name="shiroFilter")
	public ShiroFilterFactoryBean shiroFilter() {
		logger.info("执行了shiroFilter()方法。。。。");
		ShiroFilterFactoryBean bean = new ShiroFilterFactoryBean();
		bean.setSecurityManager(securityManager());
		bean.setLoginUrl("/login.jsp"); //设置登入地址
		bean.setUnauthorizedUrl("/unauthor.jsp"); //设置未授权的地址	
		
		Map<String , Filter> filters = Maps.newHashMap();
		
		filters.put("perms",urlPermissionsFilter()); //设置需要验证的信息
		filters.put("anon", new AnonymousFilter()); //设置不需要验证的信息
		
		bean.setFilters(filters); //添加是否需要验证的信息
		
		Map<String,String> chains = Maps.newHashMap();
		chains.put("/login", "anon");
		chains.put("/css/**", "anon");
		chains.put("/js/**", "anon");
		chains.put("/**", "authc");
		
		bean.setFilterChainDefinitionMap(chains); //添加Map集合，用于判断需要验证的路径
		
		return bean;
	}
	
	

	//权限管理器
	@Bean(name="securityManager")
	public DefaultWebSecurityManager securityManager() {
		logger.info("执行了securityManager()方法。。。。");
		DefaultWebSecurityManager manager = new DefaultWebSecurityManager();
		//数据库认证的实现
		manager.setRealm(myRealm());
		//session 管理器
		manager.setSessionManager(sessionManager());
		//缓存 管理器
		//manager.setCacheManager(cacheManager);
		return manager;
	}
	
	//配置自定义的Realm
	@Bean
	public MyRealm myRealm() {
		logger.info("执行了myRealm()方法。。。。");
		MyRealm myRealm = new MyRealm();
//		myRealm.setCacheManager(redisCacheManager());
//		myRealm.setCachingEnabled(true);
//		myRealm.setAuthenticationCachingEnabled(false);//禁用认证缓存
//		myRealm.setAuthorizationCachingEnabled(true);
		return myRealm;
	}
	
	//配置session的会话管理(使用web默认的session)
	@Bean(name="sessionManager")
	public ServletContainerSessionManager sessionManager() {
		logger.info("执行了sessionManager()方法。。。。");
		ServletContainerSessionManager sessionManager = new ServletContainerSessionManager();
		return sessionManager;
	}
	
	@Bean
	public URLPermissionsFilter urlPermissionsFilter() {
		logger.info("执行urlPermissionsFilter()方法。。。。");
		return new URLPermissionsFilter();
	}
	
	
}
